package com.lagou.edu.controller;

import com.lagou.edu.client.AuthCodeClient;
import com.lagou.edu.dao.LagouUserDao;
import com.lagou.edu.dao.UserTokenDao;
import com.lagou.edu.pojo.LagouUser;
import com.lagou.edu.pojo.UserToken;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixCommand;
import com.netflix.hystrix.contrib.javanica.annotation.HystrixProperty;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.data.domain.Example;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.util.List;
import java.util.UUID;

/**
 * 该类用于模拟，我们要使用共享的那些配置信息做一些事情
 */
@RestController
@RequestMapping("/user")
@RefreshScope
public class UserController {

    @Autowired
    private AuthCodeClient authCodeClient;
    @Autowired
    private LagouUserDao lagouUserDao;
    @Autowired
    private UserTokenDao userTokenDao;

    @Autowired
    private HttpServletRequest request;

    @HystrixCommand(
            // 线程池标识，要保持唯一，不唯一的话就共用了
            threadPoolKey = "findResumeOpenStateTimeoutFallback",
            // 线程池细节属性配置
            threadPoolProperties = {
                    @HystrixProperty(name="coreSize",value = "2"), // 线程数
                    @HystrixProperty(name="maxQueueSize",value="20") // 等待队列长度
            },
            // commandProperties熔断的一些细节属性配置
            commandProperties = {
                    // 每一个属性都是一个HystrixProperty
                    @HystrixProperty(name="execution.isolation.thread.timeoutInMilliseconds",value="2000"),
                    // hystrix高级配置，定制工作过程细节
                    // 统计时间窗口定义
                    @HystrixProperty(name = "metrics.rollingStats.timeInMilliseconds",value = "8000"),
                    // 统计时间窗口内的最小请求数
                    @HystrixProperty(name = "circuitBreaker.requestVolumeThreshold",value = "2"),
                    // 自我修复时的活动窗口长度
                    @HystrixProperty(name = "circuitBreaker.sleepWindowInMilliseconds",value = "3000")
            },
            fallbackMethod = "myFallBack"  // 回退方法
    )
    @GetMapping("/register/{email}/{password}/{code}")
    public Boolean register(@PathVariable String email, @PathVariable String password, @PathVariable String code) {
        if (getUserByEmail(email) != null) {
            return false;
        }
        int resoult = authCodeClient.validateAuthCode(email, code);
        if (resoult == 0) {
            LagouUser user = new LagouUser();
            user.setEmail(email);
            user.setPassword(password);
            lagouUserDao.save(user);
            return true;
        }
        return false;
    }

    Boolean myFallBack(String email, String password, String code) {
        System.out.println("请求超频");
        return false;
    }

    @GetMapping("/isRegister/{email}")
    public Boolean isRegister(@PathVariable String email) {
        return getUserByEmail(email) != null;
    }

    @GetMapping("/login/{email}/{password}")
    public String login(@PathVariable String email, @PathVariable String password) {
        LagouUser user = getUserByEmail(email);
        if (null == user) {
            return "";
        }
        if (!user.getPassword().equals(password)) {
            return "";
        }
        String uuid =  UUID.randomUUID().toString();
        UserToken token = new UserToken();
        token.setEmail(email);
        token.setToken(uuid);
        userTokenDao.save(token);

        return uuid;
    }


    @GetMapping("/info/{token}")
    public String info(@PathVariable String token) {
        UserToken userToken = getUserInfoByToken(token);
        if (null == userToken) {
            return null;
        }
        return userToken.getEmail();
    }


    private LagouUser getUserByEmail(String email){
        LagouUser user = new LagouUser();
        user.setEmail(email);
        Example<LagouUser> example = Example.of(user);
        List<LagouUser> list = lagouUserDao.findAll(example);
        if (CollectionUtils.isEmpty(list)) {
            return null;
        }
        return list.get(0);
    }


    private UserToken getUserInfoByToken(String token){
        UserToken userToken = new UserToken();
        userToken.setToken(token);
        Example<UserToken> example = Example.of(userToken);
        List<UserToken> list = userTokenDao.findAll(example);
        if (CollectionUtils.isEmpty(list)) {
            return null;
        }
        return list.get(0);
    }

}
